package com.nb.mapper;

import com.nb.dto.patient.AppointmentDTO;
import com.nb.dto.patient.PatientInfoDTO;
import com.nb.dto.patient.ScheduleOverviewDTO;
import com.nb.vo.patient.*;
import org.apache.ibatis.annotations.MapKey;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;

import java.util.List;
import java.util.Map;

/**
 * 患者数据访问层接口
 * 用于处理与患者相关的数据库操作
 */
@Mapper
@Repository
public interface PatientMapper {

    /**
     * 插入患者基本信息（通常在用户注册时调用）
     * @param params 包含 userId, name 等信息的 Map
     */
    void insertPatientInfo(Map<String, Object> params);

    /**
     * 根据用户ID获取患者信息
     * @param currentId 当前用户ID
     * @return 患者信息视图对象
     */
    PatientInfoVO getById(Integer currentId);

    /**
     * 更新患者个人信息
     * @param patientInfoDTO 患者信息数据传输对象
     */
    void updatePatientInfo(PatientInfoDTO patientInfoDTO);

    /**
     * 获取所有号源列表
     * @return 号源查询视图对象列表
     */
    List<SourceQueryVO> getNumberSourceList();

    /**
     * 获取指定患者的所有预约订单
     * @param currentId 当前用户ID
     * @return 订单视图对象列表
     */
    List<OrderVO> getAllOrdersList(Integer currentId);

    /**
     * 根据订单ID更新订单状态
     * @param id 订单ID
     */
    void updateOrderStatusById(String id);

    /**
     * 获取用户最近的一次挂号记录
     * @param currentId 当前用户ID
     * @return 最近挂号记录视图对象
     */
    LatestRegistrationVO getLatestRegistrationByUserId(Integer currentId);

    /**
     * 获取所有科室列表
     * @return 科室视图对象列表
     */
    List<DepartmentVO> getDepartmentList();

    /**
     * 根据科室ID获取科室详情
     * @param id 科室ID
     * @return 科室详情视图对象
     */
    DepartmentDetailVO getDepartmentDetailByDepartmentId(String id);

    /**
     * 根据科室ID获取该科室所有医生
     * @param id 科室ID
     * @return 科室医生视图对象列表
     */
    List<DepartmentDoctorVO> getDepartmentDoctorByDepartmentId(String id);

    /**
     * 获取排班概览信息
     * @param scheduleOverviewDTO 排班概览数据传输对象
     * @return 排班概览视图对象列表
     */
    List<ScheduleOverviewVO> getScheduleOverview(ScheduleOverviewDTO scheduleOverviewDTO);

//    /**
//     * 获取指定科室和日期的上午时间段
//     * @param departmentId 科室ID
//     * @param date 日期
//     * @return 上午时间段列表
//     */
//    List<ScheduleDetailVO.TimeSlot> getMorningTimeSlots(String departmentId, String date);
//
//    /**
//     * 获取指定科室和日期的下午时间段
//     * @param departmentId 科室ID
//     * @param date 日期
//     * @return 下午时间段列表
//     */
//    List<ScheduleDetailVO.TimeSlot> getAfternoonTimeSlots(String departmentId, String date);

    /**
     * 获取指定科室和日期的所有时间段
     * @param departmentId 科室ID
     * @param date 日期
     * @return 所有时间段列表
     */
    List<ScheduleDetailVO.TimeSlot> getAllTimeSlots(String departmentId, String date);


    /**
     * 获取指定科室和日期的可用医生
     * @param departmentId 科室ID
     * @param date 日期
     * @return 可用医生列表
     */
    List<ScheduleDetailVO.Doctor> getAvailableDoctors(String departmentId, String date);

    /**
     * 获取医生在指定日期的可用时间段
     * @param doctorId 医生ID
     * @param date 日期
     * @return 可用时间段ID列表
     */
    String getDoctorAvailableSlots(String doctorId, String date);

    /**
     * 根据医生ID和时间段ID更新号源信息
     * @param appointmentDTO 预约数据传输对象
     */
    void updateSourceByDoctorIdAndTimeId(AppointmentDTO appointmentDTO);

    /**
     * 插入挂号订单记录
     * @param appointmentDTO 预约数据传输对象
     */
    void insertRegistrationOrder(AppointmentDTO appointmentDTO);

    /**
     * 根据用户ID获取患者ID
     * @param userId 用户ID
     * @return 患者ID
     */
    String getPatientIdByUserId(Integer userId);

    /**
     * 根据医生ID和时间段ID获取号源ID
     * @param appointmentDTO 预约数据传输对象
     * @return 号源ID
     */
    String getSourceIdByDoctorIdAndTimeId(AppointmentDTO appointmentDTO);

    /**
     * 根据订单编号获取挂号订单信息
     * @param orderNo 订单编号
     * @return 挂号订单信息
     */
    Map<String, Object> getRegistrationOrderByOrderNo(String orderNo);

    /**
     * 插入医疗记录
     * @param params 医疗记录参数
     */
    void insertMedicalRecord(Map<String, Object> params);

    /**
     * 获取刚刚插入的医疗记录ID
     * @param orderId 订单ID
     * @return 医疗记录ID
     */
    Integer getMedicalRecordIdByOrderId(Object orderId);

    /**
     * 插入检查申请记录
     * @param params 检查申请参数
     */
    void insertExaminationApplication(Map<String, Object> params);

    /**
     * 插入处方记录
     * @param params 处方参数
     */
    void insertPrescription(Map<String, Object> params);

    /**
     * 插入医疗建议记录
     * @param medicalAdviceParams 医疗建议参数
     */
    void insertmedicalAdvice(Map<String, Object> medicalAdviceParams);
}